/*
 * @[H]:  Copyright (c) 2021 Phytium Information Technology, Inc. 
 * 
 *  SPDX-License-Identifier: Apache-2.0. 
 * 
 * @Date: 2021-07-14 18:29:25
 * @LastEditTime: 2021-08-16 15:54:19
 * @Description:  Description of file
 * @Modify History: 
 * * * Ver   Who        Date         Changes
 * * ----- ------     --------    --------------------------------------
 */

#include "f_spi.h"
#include "f_spi_hw.h"

#include "ft_debug.h"
#define FSPI_OP_DEBUG_TAG "FSPI_OP"
#define FSPI_OP_ERROR(format, ...) FT_DEBUG_PRINT_E(FSPI_OP_DEBUG_TAG, format, ##__VA_ARGS__)
#define FSPI_OP_DEBUG_I(format, ...) FT_DEBUG_PRINT_I(FSPI_OP_DEBUG_TAG, format, ##__VA_ARGS__)
#define FSPI_OP_DEBUG_W(format, ...) FT_DEBUG_PRINT_W(FSPI_OP_DEBUG_TAG, format, ##__VA_ARGS__)

ft_error_t FSpiSetOptions(FSpi *instance_p, u32 options, u32 value)
{
    FT_ASSERTNONVOID(instance_p != NULL);
    FT_ASSERTNONVOID(instance_p->is_ready == FT_COMPONENT_IS_READY);
    FSpiConfig *config_p;
    config_p = &instance_p->config;
    FSpiEnableChip(config_p->base_address, 0);
    switch (options)
    {
    case FSPI_OPTION_SPEED:
    {
        uint32_t clk_div;
        if (value > config_p->module_frequency)
        {
            value = config_p->module_frequency;
        }

        clk_div = FSPI_FREQ / value;
        FSPI_WRITEREG32(config_p->base_address, FSPI_BAUD_R_OFFSET, clk_div);
    }
    break;
    case FSPI_OPTION_N_BYTES:
    {
        if (value <= 2)
        {
            config_p->n_bytes = value;
        }
        else
        {
            FSPI_OP_DEBUG_W(" FSPI_OPTION_N_BYTES value %lx is not valid", value);
            goto error_return;
        }
        break;
    }
    case FSPI_OPTION_TRANS_MODE:
    {
        if (value <= SPI_MODE_3)
        {
            config_p->spi_trans_mode = value;
        }
        else
        {
            FSPI_OP_DEBUG_W(" FSPI_OPTION_TRANS_MODE value %lx is not valid", value);
            goto error_return;
        }
        break;
    }
    case FSPI_OPTION_WORK_MODE:
    {
        if (value <= FSPI_INTR_TRANSACTION)
        {
            config_p->work_mode = value;
        }
        else
        {
            FSPI_OP_DEBUG_W(" FSPI_OPTION_WORK_MODE value %lx is not valid", value);
            goto error_return;
        }
        break;
    }
    }
    FSpiEnableChip(config_p->base_address, 1);
    return FT_SUCCESS;

error_return:
    FSpiEnableChip(config_p->base_address, 1);
    return FSPI_OP_VALUE_ERROR_STATUS;
}